package com.dingding.common.core.base.controller;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.http.HttpStatus;
import org.apache.log4j.Logger;

import com.alibaba.fastjson.JSONObject;
import com.dingding.common.core.base.dto.FacadeResult;
import com.dingding.common.core.base.dto.ResponseEntity;
import com.dingding.common.core.encrpt.RSACoder;
import com.dingding.common.core.util.DataUtil;
import com.dingding.common.core.util.JSONUtil;

public abstract class BaseController {

	private static final Logger log = Logger.getLogger(BaseController.class);

	/**
	 * 
	 * @Title: getClientData
	 * @Description:获取客户端请求数据
	 * @author CHEHUANBO
	 * 
	 */
	protected String getClientData(HttpServletRequest httpServletRequest, HttpServletResponse response) {

		// 获取客户端请求数据
		String requestData = DataUtil.getData(httpServletRequest);
		// 执行解密
		String decipherData = null;
		try {
			decipherData = RSACoder.decryptByPrivateKey(requestData);
		} catch (Exception e) {
			log.error("解密数据出现异常！", e);
			response.setStatus(HttpStatus.SC_GONE);
		}
		log.info("客户端请求的数据为：" + decipherData);
		return decipherData;
	}

	/**
	 * 
	 * @Title: getRequestBean 
	 * @param clazz
	 * @return  T 转换后的业务处理bean
	 * @author CHEHAUNBO
	 * 
	 */
	protected <T> T getRequestBean(HttpServletRequest httpServletRequest, HttpServletResponse response,
			Class<T> clazz) {

		String requestData = this.getClientData(httpServletRequest, response);

		JSONObject jsonObject = JSONUtil.parseObject(requestData);
		return JSONUtil.parseObject(jsonObject.getString("requestBody"), clazz);

	}

	/**
	 * 
	 * 数据加密并且响应 给客户端
	 * 
	 * @Title: responseData
	 * @param response
	 * @param data
	 * @author CHEHAUNBO
	 * 
	 */
	protected void responseData(HttpServletResponse response, String responseData) {

		log.info("响应给客户端的数据为：" + responseData);

		try {
			response.getWriter().write(RSACoder.encryptByPublicKey(responseData));
		} catch (Exception e) {
			log.error("加密数据出现异常！", e);
			response.setStatus(HttpStatus.SC_INTERNAL_SERVER_ERROR);
		}
	}

	/**
	 * 
	 * 数据加密并且响应 给客户端
	 * 
	 * @Title: responseData
	 * @param response
	 * @param data
	 * @author CHEHAUNBO
	 * 
	 */
	protected <T> void responseData(HttpServletResponse response, ResponseEntity<T> responseEntity) {

		try {

			String responseData = JSONUtil.toJSONString(responseEntity);
			response.getWriter().write(RSACoder.encryptByPublicKey(responseData));
			log.info("响应给客户端的数据为：" + responseData);

		} catch (Exception e) {
			log.error("加密数据出现异常！", e);
			response.setStatus(HttpStatus.SC_INTERNAL_SERVER_ERROR);
		}
	}
	
	/**
	 * @Description:封装成功的返回信息
	 * @author fengshuonan
	 * @since 2.4
	 */
	@SuppressWarnings("all")
	protected void generateSuccessResponse(HttpServletResponse response,ResponseEntity responseEntity,Object obj){
		responseEntity.setCode(HttpStatus.SC_OK);
		responseEntity.setPromptMessage("请求成功");
		responseEntity.setResponseBody(obj);
		this.responseData(response, responseEntity);
	}
	
	/**
	 * @Description:封装请求参数为空的响应
	 * @author fengshuonan
	 * @since 2.4
	 */
	protected void generateNullParamRes(HttpServletResponse response){
		ResponseEntity<?> responseEntity = new ResponseEntity<>();
		responseEntity.setCode(HttpStatus.SC_BAD_REQUEST);
		responseEntity.setPromptMessage("请求参数为空");
		this.responseData(response, responseEntity);
	}
	
	/**
	 * @Description:封装错误信息
	 * @author fengshuonan
	 * @since 2.4
	 */
	@SuppressWarnings("all")
	protected void generateErrorResponse(HttpServletResponse response,int code,String message){
		ResponseEntity responseEntity = new ResponseEntity();
		responseEntity.setCode(code);
		responseEntity.setErrorMessage(message);
		this.responseData(response, responseEntity);
	}
	
	/**
	 * @Description:封装facade的返回结果
	 * @author fengshuonan
	 * @since 2.4
	 */
	@SuppressWarnings({ "rawtypes", "unchecked" })
	protected void generateFacadeResponse(HttpServletResponse response,
			ResponseEntity responseEntity,FacadeResult facadeResult){
		responseEntity.setCode(facadeResult.getCode());
		responseEntity.setErrorMessage(facadeResult.getMessage());
		responseEntity.setPromptMessage(facadeResult.getMessage());
		responseEntity.setResponseBody(facadeResult.getObject());
		this.responseData(response, responseEntity);
	}
}
